home *** CD-ROM | disk | FTP | other *** search
/ Celestin Apprentice 7 / Apprentice-Release7.iso / Environments / Open Prolog 1.0.3d33 / External Predicates… / Sources / prlxLibraries.p < prev    next >
Text File  |  1996-02-12  |  34KB  |  1,126 lines

  1. {$D+} { MacsBug symbols on }
  2. {$R-} { No range checking }
  3.  
  4. UNIT prlxLibraries;
  5.  
  6.   INTERFACE
  7.  
  8.     USES types, lowMem, quickdraw, traps,segLoad,gestaltEqu, standardFile,toolUtils,
  9.     textUtils, prlxdefinitions;
  10.  
  11.     TYPE
  12.  
  13.       oeAction = (oeDoNothing, oeCloseFile, oeCloseResFile, oeDeleteFile,
  14.                   oeDisposHandle, oeDisposPtr);
  15.       oeRecHdl = ^oeRecPtr;
  16.       oeRecPtr = ^oeRec;
  17.       oeRec = RECORD
  18.                 action: oeAction;
  19.                 parameter: longint;
  20.                 next: oeRecHdl;
  21.               END;
  22.  
  23.     PROCEDURE addOE(VAR list: oeRecHdl;
  24.                     action: oeAction;
  25.                     parameter: longint);
  26.  
  27.     FUNCTION removeOE(VAR list: oeRecHdl;
  28.                       action: oeAction;
  29.                       parameter: longint): osErr;
  30.  
  31.     FUNCTION doOE(VAR list: oeRecHdl): osErr;
  32.  
  33.     PROCEDURE initOE(VAR list: oeRecHdl);
  34.  
  35.     FUNCTION terminateOE(VAR list: oeRecHdl): osErr;
  36.  
  37.     FUNCTION TrapAvailable(tNumber: integer;
  38.                            tType: TrapType): boolean;
  39.  
  40.     FUNCTION getStringNumber(id, index: integer): longint;
  41.  
  42.     FUNCTION walkAList(list: termIndex;
  43.                        VAR head, tail: termIndex;
  44.                        plist: prlxptr): boolean;
  45.  
  46.     FUNCTION textOfAtomicList(termnumber: termindex;
  47.                               plist: prlxPtr): str255;
  48.  
  49.     FUNCTION openPrologResFile(plist: prlxPtr): integer;
  50.  
  51.     FUNCTION returnString(termNumber: termIndex;
  52.                           st: str255;
  53.                           plist: prlxPtr): boolean;
  54.  
  55.     PROCEDURE openPrologDialogFilter(VAR i: integer;
  56.                                      plist: prlxPtr);
  57.  
  58.     PROCEDURE writestr(st: str255;
  59.                        plist: prlxPtr);
  60.  
  61.     PROCEDURE writelnstr(st: str255;
  62.                          plist: prlxPtr);
  63.  
  64.     PROCEDURE errorstr(st: str255;
  65.                        plist: prlxPtr);
  66.  
  67.     FUNCTION returnValue(termNumber: termIndex;
  68.                          n: longint;
  69.                          plist: prlxPtr): boolean;
  70.  
  71.     FUNCTION returnStructure(termNumber: termIndex;
  72.                              st: str255;
  73.                              arity: integer;
  74.                              plist: prlxPtr): boolean;
  75.  
  76.     FUNCTION returnList(termNumber: termIndex;
  77.                         plist: prlxPtr): boolean;
  78.  
  79.     FUNCTION returnAtom(termNumber: termIndex;
  80.                         st: str255;
  81.                         plist: prlxPtr): boolean;
  82.  
  83.     FUNCTION returnUnifiedTerms(a, b: termIndex;
  84.                                 plist: prlxPtr): boolean;
  85.  
  86.     FUNCTION subterm(subtermordinate: integer;
  87.                      termNumber: termIndex;
  88.                      plist: prlxPtr): termIndex;
  89.  
  90.     FUNCTION listItem(listItemOrdinate: integer;
  91.                       termNumber: termIndex;
  92.                       plist: prlxPtr): termIndex;
  93.  
  94.     FUNCTION newFreeTerm(plist: prlxPtr): termIndex;
  95.  
  96.     FUNCTION number(termNumber: termIndex;
  97.                     plist: prlxPtr): boolean;
  98.  
  99.     FUNCTION atom(termNumber: termIndex;
  100.                   plist: prlxPtr): boolean;
  101.  
  102.     FUNCTION structure(termNumber: termIndex;
  103.                        plist: prlxPtr): boolean;
  104.  
  105.     FUNCTION list(termNumber: termIndex;
  106.                   plist: prlxPtr): boolean;
  107.  
  108.     FUNCTION variable(termNumber: termIndex;
  109.                       plist: prlxPtr): boolean;
  110.  
  111.     FUNCTION value(termNumber: termIndex;
  112.                    plist: prlxPtr): longint;
  113.  
  114.     FUNCTION arity(termNumber: termIndex;
  115.                    plist: prlxPtr): integer;
  116.  
  117.     FUNCTION text(termNumber: termIndex;
  118.                   plist: prlxPtr): str255;
  119.  
  120.     FUNCTION drawAlert(ALRTid: integer;
  121.                        st: str255;
  122.                        plist: prlxPtr): longint;
  123.  
  124.     FUNCTION centreDialog(DLOGid: integer;
  125.                           plist: prlxPtr): longint;
  126.  
  127.     PROCEDURE centreSfGetTEXTFile(vertical: integer;
  128.                                   str: str255;
  129.                                   VAR reply: sfReply);
  130.  
  131.     PROCEDURE centreSfPutFile(vertical: integer;
  132.                               str: str255;
  133.                               origName: str255;
  134.                               dlgHook: procPtr;
  135.                               VAR reply: sfReply);
  136.  
  137.     FUNCTION getFileName(VAR FileName: str255;
  138.                          VAR FileVolume: longint): boolean;
  139.  
  140.     FUNCTION predicateNameAndArity(VAR name: str255;
  141.                                    VAR arity: integer;
  142.                                    plist: prlxPtr): boolean;
  143.  
  144.     PROCEDURE signalError(error: integer;
  145.                           argumentIndex: integer;
  146.                           hostErrorCode: longint;
  147.                           errorMessage: str255;
  148.                           plist: prlxPtr);
  149.  
  150.     FUNCTION registerIOHandler(handlerCode: osType;
  151.                                handlerPointer: procPtr;
  152.                                plist: prlxPtr): osErr;
  153.  
  154.     FUNCTION IOObjectRegisterIsFull(plist: prlxPtr): boolean;
  155.  
  156.     FUNCTION registerIOObject(VAR objectReference: longint;
  157.                               theHandlerKindCode,theObjectType: osType;
  158.                               privateData: longint;
  159.                               isAStream: boolean;
  160.                               plist: prlxPtr): osErr;
  161.  
  162.     FUNCTION deregisterIOObject(objectReference: longint;
  163.                                 theHandlerKindCode: osType;
  164.                                 plist: prlxPtr): osErr;
  165.  
  166.     FUNCTION getIOObjectInfo(theObjectReference: longint;
  167.                              VAR theHandlerKindCode, theObjectType: osType;
  168.                              VAR privateData: longint;
  169.                              VAR isAStream: boolean;
  170.                              plist: prlxPtr): osErr;
  171.  
  172.     FUNCTION getIOObjectReference(VAR objectReference: longint;
  173.                                   handlerKindCode,theObjectType: osType;
  174.                                   privateData: longint;
  175.                                   plist: prlxPtr): osErr;
  176.  
  177.     FUNCTION countIOObjects(handlerKindCode,objectTypeCode: osType;plist: prlxPtr): longint;
  178.  
  179.     FUNCTION findIndexedIOObjectReference(VAR objectReference: longint;
  180.                                   handlerKindCode,objectTypeCode: osType;
  181.                                   index: longint;
  182.                                   plist: prlxPtr): osErr;
  183.  
  184.   IMPLEMENTATION
  185.  
  186.     PROCEDURE signalError(error: integer;
  187.                           argumentIndex: integer;
  188.                           hostErrorCode: longint;
  189.                           errorMessage: str255;
  190.                           plist: prlxPtr);
  191.  
  192.     {if you want to throw an error from an external predicate, use this}
  193.     {error kind is an index to an ISO error type - see prlxDefinitions.p}
  194.     {hostErrorCode is where you can put a mac error code}
  195. {give an argument index of -1 if you don't want it to try to output the goal's name}
  196.  
  197.       VAR
  198.         i: integer;
  199.         t, r, q: termIndex;
  200.         ignoreBoolean: boolean;
  201.         thePredicateName: str255;
  202.         thePredicateArity: integer;
  203.  
  204.       BEGIN
  205.  
  206.         WITH plist^ DO
  207.           BEGIN
  208.           outcome := error; {outcome is normally 'notAnErrorCode' - this puts a
  209.                              real error code there}
  210.           data[1] := newFreeTerm(plist);
  211.           END;
  212.         ignoreBoolean := predicateNameAndArity(thePredicateName,
  213.                                                thePredicateArity, plist);
  214.  
  215.         q := plist^.data[1];
  216.  
  217.         IF argumentIndex <> - 1 {-1 is flag to not even try to output the goal's
  218.                                  name}
  219.            THEN
  220.           BEGIN
  221.           ignoreBoolean := returnList(q, plist); {return a list of error
  222.                                                   information}
  223.           r := subterm(1, q, plist);
  224.           ignoreBoolean := returnStructure(r, 'goal', 1, plist); {first, the
  225.             goal - functor & arguments}
  226.           r := subterm(1, r, plist);
  227.           ignoreBoolean := returnStructure(r, thePredicateName,
  228.                                            thePredicateArity, plist);
  229.           FOR i := 1 TO thePredicateArity DO
  230.             ignoreBoolean := returnUnifiedTerms(subterm(i, r, plist), i, plist);{the
  231.             goal's arguments}
  232.           q := subterm(2, q, plist);
  233.           END;
  234.  
  235.         IF argumentIndex > 0 {if the argument index is 0 or -1, no argument
  236.                               index info returned}
  237.            THEN
  238.           BEGIN
  239.           ignoreBoolean := returnList(q, plist);
  240.           r := subterm(1, q, plist);
  241.           ignoreBoolean := returnStructure(r, 'argument_index', 1, plist);
  242.           r := subterm(1, r, plist);
  243.           ignoreBoolean := returnValue(r, argumentIndex, plist);
  244.           q := subterm(2, q, plist);
  245.           END;
  246.  
  247.         IF hostErrorCode <> 0 {if the mac error code = 0, no host error info
  248.                                returned}
  249.            THEN
  250.           BEGIN
  251.           ignoreBoolean := returnList(q, plist);
  252.           r := subterm(1, q, plist);
  253.           ignoreBoolean := returnStructure(r, 'host_error_code', 1, plist);
  254.           r := subterm(1, r, plist);
  255.           ignoreBoolean := returnValue(r, hostErrorCode, plist);
  256.           q := subterm(2, q, plist);
  257.           END;
  258.  
  259.         IF errorMessage <> '' {only return an error message term if it's
  260.                                non-blank}
  261.            THEN
  262.           BEGIN
  263.           ignoreBoolean := returnList(q, plist);
  264.           r := subterm(1, q, plist);
  265.           ignoreBoolean := returnStructure(r, 'error_message', 1, plist);
  266.           r := subterm(1, r, plist);
  267.           ignoreBoolean := returnAtom(r, errorMessage, plist);
  268.           q := subterm(2, q, plist);
  269.           END;
  270.  
  271.         ignoreBoolean := returnAtom(q, '[]', plist); {terminate the list}
  272.       END;
  273.  
  274.     PROCEDURE addOE(VAR list: oeRecHdl;
  275.                     action: oeAction;
  276.                     parameter: longint);
  277.  
  278.       VAR
  279.         temp: oeRecHdl;
  280.  
  281.       BEGIN
  282.         temp := oeRecHdl(newHandleClear(sizeOf(oeRec)));
  283.         temp^^.next := list;
  284.         list := temp;
  285.         list^^.action := action;
  286.         list^^.parameter := parameter;
  287.       END;
  288.  
  289.     FUNCTION existsOE(VAR list: oeRecHdl;
  290.                       action: oeAction;
  291.                       VAR parameter: longint): boolean;
  292.  
  293.       VAR
  294.         temp: oeRecHdl;
  295.         found: boolean;
  296.  
  297.       BEGIN
  298.         temp := list;
  299.         found := false;
  300.         REPEAT
  301.           IF temp <> NIL THEN
  302.             BEGIN
  303.             IF temp^^.action = action THEN
  304.               found := true
  305.             ELSE
  306.               temp := temp^^.next;
  307.             END;
  308.         UNTIL (temp = NIL) OR found;
  309.         IF found THEN parameter := temp^^.parameter;
  310.         existsOE := found;
  311.       END;
  312.  
  313.     FUNCTION removeOE(VAR list: oeRecHdl;
  314.                       action: oeAction;
  315.                       parameter: longint): osErr;
  316.  
  317.       VAR
  318.         temp: oeRecHdl;
  319.         found: boolean;
  320.  
  321.       BEGIN
  322.         temp := list;
  323.         REPEAT
  324.           IF temp <> NIL THEN
  325.             BEGIN
  326.             found := (temp^^.action = action) AND (temp^^.parameter =
  327.                      parameter);
  328.             IF NOT found THEN temp := temp^^.next;
  329.             END;
  330.         UNTIL (temp = NIL) OR found;
  331.         IF found THEN
  332.           BEGIN
  333.           removeOE := noErr;
  334.           temp^^.action := oeDoNothing;
  335.           END
  336.         ELSE
  337.           removeOE := paramErr;
  338.       END;
  339.  
  340.     FUNCTION doOE(VAR list: oeRecHdl): osErr;
  341.  
  342.       TYPE
  343.         fssSpecPtr = ^fsSpec;
  344.  
  345.       VAR
  346.         temp: oeRecHdl;
  347.         thePort: grafPtr;
  348.         errorCode: osErr;
  349.  
  350.       BEGIN
  351.         errorCode := noErr;
  352.         WHILE (list <> NIL) AND (errorCode = noErr) DO
  353.           WITH list^^ DO
  354.             BEGIN
  355.             hLock(handle(list));
  356.             CASE action OF
  357.               oeDoNothing: ;
  358.               oeCloseFile: errorCode := fsClose(parameter);
  359.               oeCloseResFile:
  360.                 BEGIN
  361.                 closeResFile(parameter);
  362.                 errorCode := resError;
  363.                 END;
  364.               oeDeleteFile: errorCode := fSpDelete(fssSpecPtr(parameter)^);
  365.               oeDisposHandle:
  366.                 BEGIN
  367.                 disposHandle(handle(parameter));
  368.                 errorCode := memError;
  369.                 END;
  370.               oeDisposPtr:
  371.                 BEGIN
  372.                 disposPtr(ptr(parameter));
  373.                 errorCode := memError;
  374.                 END;
  375.             END;
  376.             IF errorCode = noErr THEN
  377.               BEGIN
  378.               temp := list^^.next;
  379.               disposHandle(handle(list));
  380.               list := temp;
  381.               END;
  382.             END;
  383.       END;
  384.  
  385.     PROCEDURE initOE(VAR list: oeRecHdl);
  386.  
  387.       BEGIN
  388.         list := NIL;
  389.       END;
  390.  
  391.     FUNCTION terminateOE(VAR list: oeRecHdl): osErr;
  392.  
  393.       VAR
  394.         temp: oeRecHdl;
  395.         result: osErr;
  396.  
  397.       BEGIN
  398.         result := 0;
  399.         WHILE list <> NIL DO
  400.           BEGIN
  401.           IF list^^.action <> oeDoNothing THEN result := paramErr;
  402.           temp := list;
  403.           list := list^^.next;
  404.           disposHandle(handle(temp));
  405.           END;
  406.         terminateOE := result;
  407.       END;
  408.  
  409.     PROCEDURE openPrologDialogFilter(VAR i: integer;
  410.                                      plist: prlxPtr);
  411.  
  412.       VAR
  413.         l: longint;
  414.  
  415.       BEGIN
  416.         WITH plist^ DO
  417.           BEGIN
  418.           callbackrequest := doMyModalDialog;
  419.           callback(entrypoint);
  420.           l := callbackdata[1];
  421.           i := l;
  422.           END;
  423.       END;
  424.  
  425.     FUNCTION TrapAvailable(tNumber: integer;
  426.                            tType: TrapType): boolean;
  427.  
  428. {Check to see if a given trap is implemented.
  429.  The recommended approach to see if a trap is implemented is to see if
  430.  the address of the trap routine is the same as the address of the
  431.  Unimplemented trap.}
  432.  
  433.       VAR
  434.         gMac: sysEnvRec;
  435.         errCode: osErr;
  436.  
  437.       BEGIN
  438.         errCode := noErr;
  439.         IF (tType = ToolTrap) THEN
  440.           BEGIN
  441.           errCode := sysEnvirons(1, gMac);
  442.           IF (errCode = noErr) & (gMac.machineType > envMachUnknown) &
  443.              (gMac.machineType < envMacII) THEN
  444.             BEGIN {it's a 512KE, Plus, or SE}
  445.             tNumber := BAND(tNumber, $03FF);
  446.             IF tNumber > $01FF THEN {which means the tool traps}
  447.               tNumber := _Unimplemented; {only go to $01FF}
  448.             END;
  449.           END;
  450.         TrapAvailable := (NGetTrapAddress(tNumber, tType) <>
  451.                          GetTrapAddress(_Unimplemented)) AND (errCode = noErr);
  452.       END; {TrapAvailable}
  453.  
  454.     FUNCTION getStringNumber(id, index: integer): longint;
  455.  
  456.       VAR
  457.         s: Str255;
  458.         n: longint;
  459.         i: integer;
  460.  
  461.       BEGIN
  462.         getIndString(s, id, index);
  463.         i := 1;
  464.         n := 0;
  465.         IF length(s) <> 0 THEN
  466.           WHILE (i <= length(s)) AND (s[i] IN ['0'..'9']) DO
  467.             BEGIN
  468.             n := n * 10 + ord(s[i]) - ord('0');
  469.             i := i + 1;
  470.             END;
  471.         getStringNumber := n;
  472.       END;
  473.  
  474.     FUNCTION walkAList(list: termIndex;
  475.                        VAR head, tail: termIndex;
  476.                        plist: prlxptr): boolean;
  477.  
  478.       BEGIN
  479.         IF (text(list, plist) = '.') AND (arity(list, plist) = 2) THEN
  480.           BEGIN
  481.           walkAList := true;
  482.           head := subTerm(1, list, plist);
  483.           tail := subTerm(2, list, plist);
  484.           END
  485.         ELSE
  486.           walkAList := false;
  487.       END;
  488.  
  489.     FUNCTION openPrologResFile(plist: prlxPtr): integer;
  490.  
  491.       BEGIN
  492.         WITH plist^ DO
  493.           BEGIN
  494.           callbackrequest := getHomeResFileID;
  495.           callback(entrypoint);
  496.           openPrologResFile := callbackdata[1];
  497.           END;
  498.       END;
  499.  
  500.     FUNCTION textOfAtomicList(termnumber: termindex;
  501.                               plist: prlxPtr): str255;
  502.  
  503.       VAR
  504.         st: str255;
  505.         i: integer;
  506.         p, q: ptr;
  507.         v: longint;
  508.  
  509.       BEGIN
  510.         i := 0;
  511.         p := ptr(longint(@st) + 1);
  512.         q := ptr(longint(@v) + 3);
  513.         WHILE (text(termNumber, plist) = '.') AND (arity(termNumber, plist) =
  514.               2) DO
  515.           BEGIN
  516.           IF i <> 255 THEN
  517.             BEGIN
  518.             v := value(subterm(1, termNumber, plist), plist);
  519.             i := i + 1;
  520.             p^ := q^;
  521.             p := ptr(longint(p) + 1);
  522.             END;
  523.           termNumber := subterm(2, termNumber, plist);
  524.           END;
  525.         p := @st;
  526.         q := ptr(longint(@i) + 1);
  527.         p^ := q^;
  528.         textOfAtomicList := st;
  529.       END;
  530.  
  531.     FUNCTION returnString(termNumber: termIndex;
  532.                           st: str255;
  533.                           plist: prlxPtr): boolean;
  534.  
  535.       VAR
  536.         continue: boolean;
  537.         i: integer;
  538.         runningTerm: termIndex;
  539.  
  540.       BEGIN
  541.         runningTerm := termNumber;
  542.         continue := true;
  543.         IF st <> '' THEN
  544.           FOR i := 1 TO length(st) DO
  545.             BEGIN
  546.             IF continue THEN
  547.               continue := returnStructure(runningTerm, '.', 2, plist);
  548.             IF continue THEN
  549.               continue := returnValue(subterm(1, runningTerm, plist),
  550.                                       ord(st[i]), plist);
  551.             IF continue THEN runningTerm := subterm(2, runningTerm, plist);
  552.             END;
  553.         IF continue THEN continue := returnAtom(runningTerm, '[]', plist);
  554.         returnString := continue;
  555.       END;
  556.  
  557.     PROCEDURE writestr(st: str255;
  558.                        plist: prlxPtr);
  559.  
  560.       BEGIN
  561.         WITH plist^ DO
  562.           BEGIN
  563.           callbackrequest := writestring;
  564.           s := st;
  565.           callback(entrypoint);
  566.           END;
  567.       END;
  568.  
  569.     PROCEDURE writelnstr(st: str255;
  570.                          plist: prlxPtr);
  571.  
  572.       BEGIN
  573.         WITH plist^ DO
  574.           BEGIN
  575.           callbackrequest := writelnstring;
  576.           s := st;
  577.           callback(entrypoint);
  578.           END;
  579.       END;
  580.  
  581.     PROCEDURE errorstr(st: str255;
  582.                        plist: prlxPtr);
  583.  
  584.       BEGIN
  585.         WITH plist^ DO
  586.           BEGIN
  587.           callbackrequest := writeerror;
  588.           s := st;
  589.           callback(entrypoint);
  590.           END;
  591.       END;
  592.  
  593.     FUNCTION predicateNameAndArity(VAR name: str255;
  594.                                    VAR arity: integer;
  595.                                    plist: prlxPtr): boolean;
  596.  
  597.       BEGIN
  598.         WITH plist^ DO
  599.           BEGIN
  600.           callbackrequest := getPredicateNameAndArity;
  601.           callback(entrypoint);
  602.           predicateNameAndArity := callbackData[3] = messageOK;
  603.           name := s;
  604.           arity := callbackData[1];
  605.           END;
  606.       END;
  607.  
  608.     FUNCTION returnUnifiedTerms(a, b: termIndex;
  609.                                 plist: prlxPtr): boolean;
  610.  
  611.       BEGIN
  612.         WITH plist^ DO
  613.           BEGIN
  614.           callbackrequest := unifyTerms;
  615.           callbackData[1] := a;
  616.           callbackData[2] := b;
  617.           callback(entrypoint);
  618.           returnUnifiedTerms := callbackData[3] = messageOK;
  619.           END;
  620.       END;
  621.  
  622.     FUNCTION returnValue(termNumber: termIndex;
  623.                          n: longint;
  624.                          plist: prlxPtr): boolean;
  625.  
  626.       BEGIN
  627.         WITH plist^ DO
  628.           BEGIN
  629.           callbackrequest := unifyToInteger;
  630.           callbackData[1] := termNumber;
  631.           callbackData[2] := n;
  632.           callback(entrypoint);
  633.           returnValue := callbackData[3] = messageOK;
  634.           END;
  635.       END;
  636.  
  637.     FUNCTION returnList(termNumber: termIndex;
  638.                         plist: prlxPtr): boolean;
  639.  
  640.       BEGIN
  641.         WITH plist^ DO
  642.           BEGIN
  643.           callbackrequest := unifyToFunctor;
  644.           callbackData[1] := termNumber;
  645.           callbackData[3] := 2;
  646.           s := '.';
  647.           callback(entrypoint);
  648.           returnList := callbackData[3] = messageOK;
  649.           END;
  650.       END;
  651.  
  652.     FUNCTION returnStructure(termNumber: termIndex;
  653.                              st: str255;
  654.                              arity: integer;
  655.                              plist: prlxPtr): boolean;
  656.  
  657.       BEGIN
  658.         WITH plist^ DO
  659.           BEGIN
  660.           callbackrequest := unifyToFunctor;
  661.           callbackData[1] := termNumber;
  662.           callbackData[3] := arity;
  663.           s := st;
  664.           callback(entrypoint);
  665.           returnStructure := callbackData[3] = messageOK;
  666.           END;
  667.       END;
  668.  
  669.     FUNCTION returnAtom(termNumber: termIndex;
  670.                         st: str255;
  671.                         plist: prlxPtr): boolean;
  672.  
  673.       BEGIN
  674.         returnAtom := returnStructure(termNumber, st, 0, plist);
  675.       END;
  676.  
  677.     FUNCTION subterm(subtermordinate: integer;
  678.                      termNumber: termIndex;
  679.                      plist: prlxPtr): termIndex;
  680.  
  681.       BEGIN
  682.         WITH plist^ DO
  683.           BEGIN
  684.           callbackrequest := getsubterm;
  685.           callbackData[1] := termNumber;
  686.           callbackData[2] := subtermordinate;
  687.           callback(entrypoint);
  688.           IF callbackData[3] = - 1 THEN
  689.             BEGIN
  690.             errorstr(
  691. 'attempt to get index of subterm of a variable or atomic term in subterm - index used is 1'
  692.                      , plist);
  693.             subterm := 1;
  694.             END
  695.           ELSE
  696.             subterm := callbackData[3];
  697.           END;
  698.       END;
  699.  
  700.     FUNCTION listItem(listItemOrdinate: integer;
  701.                       termNumber: termIndex;
  702.                       plist: prlxPtr): termIndex;
  703.  
  704.       BEGIN
  705.         WHILE listItemOrdinate > 1 DO
  706.           BEGIN
  707.           WITH plist^ DO
  708.             BEGIN
  709.             callbackrequest := getsubterm;
  710.             callbackData[1] := termNumber;
  711.             callbackData[2] := 2;
  712.             callback(entrypoint);
  713.             IF callbackData[3] = - 1 THEN
  714.               BEGIN
  715.               errorstr(
  716. 'attempt to get index of subterm of a variable or atomic term in listItem - index used is 1'
  717.                        , plist);
  718.               termNumber := 1;
  719.               END
  720.             ELSE
  721.               termNumber := callbackData[3];
  722.             END;
  723.           listItemOrdinate := listItemOrdinate - 1;
  724.           END;
  725.         WITH plist^ DO
  726.           BEGIN
  727.           callbackrequest := getsubterm;
  728.           callbackData[1] := termNumber;
  729.           callbackData[2] := 1;
  730.           callback(entrypoint);
  731.           IF callbackData[3] = - 1 THEN
  732.             BEGIN
  733.             errorstr(
  734. 'attempt to get index of subterm of a variable or atomic term in listItem - index used is 1'
  735.                      , plist);
  736.             listItem := 1;
  737.             END
  738.           ELSE
  739.             listItem := callbackData[3];
  740.           END;
  741.       END;
  742.  
  743.     FUNCTION newFreeTerm(plist: prlxPtr): termIndex;
  744.  
  745.       BEGIN
  746.         WITH plist^ DO
  747.           BEGIN
  748.           callbackrequest := getFreeTerm;
  749.           callback(entrypoint);
  750.           newFreeTerm := callbackData[1];
  751.           END;
  752.       END;
  753.  
  754.     FUNCTION number(termNumber: termIndex;
  755.                     plist: prlxPtr): boolean;
  756.  
  757.       BEGIN
  758.         WITH plist^ DO
  759.           BEGIN
  760.           callbackrequest := getterminfo;
  761.           callbackData[1] := termNumber;
  762.           callback(entrypoint);
  763.           number := (callbackData[1] = integertag);
  764.           END;
  765.       END;
  766.  
  767.     FUNCTION atom(termNumber: termIndex;
  768.                   plist: prlxPtr): boolean;
  769.  
  770.       BEGIN
  771.         WITH plist^ DO
  772.           BEGIN
  773.           callbackrequest := getterminfo;
  774.           callbackData[1] := termNumber;
  775.           callback(entrypoint);
  776.           atom := (callbackData[1] = atomtag);
  777.           END;
  778.       END;
  779.  
  780.     FUNCTION structure(termNumber: termIndex;
  781.                        plist: prlxPtr): boolean;
  782.  
  783.       BEGIN
  784.         WITH plist^ DO
  785.           BEGIN
  786.           callbackrequest := getterminfo;
  787.           callbackData[1] := termNumber;
  788.           callback(entrypoint);
  789.           structure := (callbackData[1] = structuretag);
  790.           END;
  791.       END;
  792.  
  793.     FUNCTION list(termNumber: termIndex;
  794.                   plist: prlxPtr): boolean;
  795.  
  796.       BEGIN
  797.         WITH plist^ DO
  798.           BEGIN
  799.           callbackrequest := getterminfo;
  800.           callbackData[1] := termNumber;
  801.           callback(entrypoint);
  802.           list := ((callbackData[1] = structuretag) AND (s = '.') AND
  803.                   (callbackData[3] = 2)) OR ((callbackData[1] = atomtag) AND
  804.                   (s = '[]'));
  805.           END;
  806.       END;
  807.  
  808.     FUNCTION variable(termNumber: termIndex;
  809.                       plist: prlxPtr): boolean;
  810.  
  811.       BEGIN
  812.         WITH plist^ DO
  813.           BEGIN
  814.           callbackrequest := getterminfo;
  815.           callbackData[1] := termNumber;
  816.           callback(entrypoint);
  817.           variable := (callbackData[1] = variabletag);
  818.           END;
  819.       END;
  820.  
  821.     FUNCTION value(termNumber: termIndex;
  822.                    plist: prlxPtr): longint;
  823.  
  824.       BEGIN
  825.         value := 0;
  826.         WITH plist^ DO
  827.           BEGIN
  828.           callbackrequest := getterminfo;
  829.           callbackData[1] := termNumber;
  830.           callback(entrypoint);
  831.           IF callbackData[1] = integertag THEN
  832.             value := callbackData[2]
  833.           ELSE
  834.             BEGIN
  835.             errorstr('attempt to get value of a non-integer - value used is 0',
  836.                      plist);
  837.             value := 0;
  838.             END;
  839.           END;
  840.       END;
  841.  
  842.     FUNCTION arity(termNumber: termIndex;
  843.                    plist: prlxPtr): integer;
  844.  
  845.       BEGIN
  846.         WITH plist^ DO
  847.           BEGIN
  848.           callbackrequest := getterminfo;
  849.           callbackData[1] := termNumber;
  850.           callback(entrypoint);
  851.           CASE callbackData[1] OF
  852.             atomtag, integertag, variabletag: arity := 0;
  853.             structuretag: arity := callbackData[3];
  854.             OTHERWISE errorstr('Funny data from getTermInfo in arity', plist);
  855.           END;
  856.           END;
  857.       END;
  858.  
  859.     FUNCTION text(termNumber: termIndex;
  860.                   plist: prlxPtr): str255;
  861.  
  862.       VAR
  863.         st: str255;
  864.         i: integer;
  865.  
  866.       BEGIN
  867.         WITH plist^ DO
  868.           BEGIN
  869.           callbackrequest := getterminfo;
  870.           callbackData[1] := termNumber;
  871.           callback(entrypoint);
  872.           CASE callbackData[1] OF
  873.             atomtag, structuretag: text := s;
  874.             integertag:
  875.               BEGIN
  876.               numtostring(callbackData[2], st);
  877.               text := st;
  878.               END;
  879.             variabletag:
  880.               BEGIN
  881.               numtostring(callbackData[2], st);
  882.               FOR i := 255 DOWNTO 2 DO st[i] := st[i - 1];
  883.               st[1] := '_';
  884.               text := st;
  885.               END;
  886.             OTHERWISE errorstr('Funny data from getTermInfo in text', plist);
  887.           END;
  888.           END;
  889.       END;
  890.  
  891.     FUNCTION drawAlert(ALRTid: integer;
  892.                        st: str255;
  893.                        plist: prlxPtr): longint;
  894.  
  895.       BEGIN
  896.         WITH plist^ DO
  897.           BEGIN
  898.           callbackrequest := drawALRT;
  899.           callbackData[1] := ALRTid;
  900.           s := st;
  901.           callback(entrypoint);
  902.           drawAlert := callbackData[2];
  903.           END;
  904.       END;
  905.  
  906.     FUNCTION centreDialog(DLOGid: integer;
  907.                           plist: prlxPtr): longint;
  908.  
  909.       VAR
  910.         item: integer;
  911.         myDialog: dialogPtr;
  912.  
  913.       BEGIN
  914.         WITH plist^ DO
  915.           BEGIN
  916.   (* ###hack        callbackrequest := drawDLOG;
  917.           callbackData[1] := DLOGid;
  918.            callback(entrypoint);
  919.           centreDialog := callbackData[2]; *)
  920.  
  921.           myDialog := getNewDialog(DLOGid, NIL, windowPtr(1));
  922.           showWindow(myDialog);
  923.           modalDialog(NIL, item);
  924.           disposDialog(myDialog);
  925.           centreDialog := item;
  926.           END;
  927.       END;
  928.  
  929.     PROCEDURE centreSfGetTEXTFile(vertical: integer;
  930.                                   str: str255;
  931.                                   VAR reply: sfReply);
  932.  
  933.       VAR
  934.         myPoint: point;
  935.         dialogHandle: dialogTHndl;
  936.         myPort: grafPtr;
  937.         screenWidth, dialogWidth: integer;
  938.         myTypeList: sfTypeList;
  939.  
  940.       BEGIN
  941.         myTypeList[0] := 'TEXT';
  942.         getPort(myPort);
  943.         WITH myPort^.portBits.bounds DO screenWidth := right - left;
  944.         dialogHandle := dialogTHndl(getResource('DLOG', getDlgId));
  945.         WITH dialogHandle^^.boundsRect DO
  946.           BEGIN
  947.           dialogWidth := right - left;
  948.           myPoint.h := (screenWidth - dialogWidth) DIV 2;
  949.           myPoint.v := vertical;
  950.           END;
  951.         sfGetFile(myPoint, str, NIL, 1, @myTypeList, NIL, reply);
  952.       END;
  953.  
  954.     PROCEDURE centreSfPutFile(vertical: integer;
  955.                               str: str255;
  956.                               origName: str255;
  957.                               dlgHook: procPtr;
  958.                               VAR reply: sfReply);
  959.  
  960.       VAR
  961.         myPoint: point;
  962.         dialogHandle: dialogTHndl;
  963.         myPort: grafPtr;
  964.         screenWidth, dialogWidth: integer;
  965.  
  966.       BEGIN
  967.         getPort(myPort);
  968.         WITH myPort^.portBits.bounds DO screenWidth := right - left;
  969.         dialogHandle := dialogTHndl(getResource('DLOG', putDlgId));
  970.         WITH dialogHandle^^.boundsRect DO
  971.           BEGIN
  972.           dialogWidth := right - left;
  973.           myPoint.h := (screenWidth - dialogWidth) DIV 2;
  974.           myPoint.v := vertical;
  975.           END;
  976.         sfPutFile(myPoint, str, origName, dlgHook, reply);
  977.       END;
  978.  
  979.     FUNCTION getFileName(VAR FileName: str255;
  980.                          VAR FileVolume: longint): boolean;
  981.  
  982.       VAR
  983.         reply: sfReply;
  984.  
  985.       BEGIN
  986.         centreSfGetTEXTFile(75, '', reply);
  987.         FileName := reply.fName;
  988.         FileVolume := reply.vRefNum;
  989.         getFileName := reply.good;
  990.       END;
  991.  
  992.     FUNCTION registerIOHandler(handlerCode: osType;
  993.                                handlerPointer: procPtr;
  994.                                plist: prlxPtr): osErr;
  995.  
  996.       BEGIN
  997.         WITH plist^ DO
  998.           BEGIN
  999.           callbackrequest := registerAnIOHandler;
  1000.           callbackData[1] := longint(handlerCode);
  1001.           callbackData[2] := longint(handlerPointer);
  1002.           callback(entrypoint);
  1003.           registerIOHandler := callbackRequest;
  1004.           END;
  1005.       END;
  1006.  
  1007.     FUNCTION IOObjectRegisterIsFull(plist: prlxPtr): boolean;
  1008.  
  1009.       BEGIN
  1010.         WITH plist^ DO
  1011.           BEGIN
  1012.           callbackrequest := checkIOObjectRegisterIsFull;
  1013.           callback(entrypoint);
  1014.           IOObjectRegisterIsFull := callbackData[1] = 1;
  1015.           END;
  1016.       END;
  1017.  
  1018.     FUNCTION registerIOObject(VAR objectReference: longint;
  1019.                               theHandlerKindCode,theObjectType: osType;
  1020.                               privateData: longint;
  1021.                               isAStream: boolean;
  1022.                               plist: prlxPtr): osErr;
  1023.  
  1024.       BEGIN
  1025.         WITH plist^ DO
  1026.           BEGIN
  1027.           callbackrequest := registerAnIOObject;
  1028.           callbackData[1] := longint(theHandlerKindCode);
  1029.           callbackData[2] := longint(theObjectType);
  1030.           callbackData[3] := privateData;
  1031.           IF isAStream THEN
  1032.             callbackData[4] := 1
  1033.           ELSE
  1034.             callbackData[4] := 0;
  1035.           callback(entrypoint);
  1036.           objectReference := callbackData[1];
  1037.           registerIOObject := callbackRequest;
  1038.           END;
  1039.       END;
  1040.  
  1041.     FUNCTION deregisterIOObject(objectReference: longint;
  1042.                                 theHandlerKindCode: osType;
  1043.                                 plist: prlxPtr): osErr;
  1044.  
  1045.       BEGIN
  1046.         WITH plist^ DO
  1047.           BEGIN
  1048.           callbackrequest := deRegisterAnIOObject;
  1049.           callbackData[1] := objectReference;
  1050.           callbackData[2] := longint(theHandlerKindCode);
  1051.           callback(entrypoint);
  1052.           deRegisterIOObject := callbackRequest;
  1053.           END;
  1054.       END;
  1055.  
  1056.     FUNCTION getIOObjectInfo(theObjectReference: longint;
  1057.                              VAR theHandlerKindCode, theObjectType: osType;
  1058.                              VAR privateData: longint;
  1059.                              VAR isAStream: boolean;
  1060.                              plist: prlxPtr): osErr;
  1061.  
  1062.       BEGIN
  1063.         WITH plist^ DO
  1064.           BEGIN
  1065.           callbackrequest := getAnIOObjectInfo;
  1066.           callbackData[1] := theObjectReference;
  1067.           callback(entrypoint);
  1068.           theHandlerKindCode := osType(callbackData[1]);
  1069.           theObjectType := osType(callbackData[2]);
  1070.          privateData := callbackData[3];
  1071.           isAStream := callbackData[4] = 1;
  1072.           getIOObjectInfo := callbackRequest;
  1073.           END;
  1074.       END;
  1075.  
  1076.     FUNCTION getIOObjectReference(VAR objectReference: longint;
  1077.                                   handlerKindCode,theObjectType: osType;
  1078.                                   privateData: longint;
  1079.                                   plist: prlxPtr): osErr;
  1080.  
  1081.       BEGIN
  1082.         WITH plist^ DO
  1083.           BEGIN
  1084.           callbackrequest := getAnIOObjectReference;
  1085.           callbackData[1] := longint(handlerKindCode);
  1086.           callbackData[2] := longint(theObjectType);
  1087.           callbackData[3] := privateData;
  1088.           callback(entrypoint);
  1089.           objectReference := callbackData[1];
  1090.           getIOObjectReference := callbackRequest;
  1091.           END;
  1092.       END;
  1093.  
  1094.     FUNCTION countIOObjects(handlerKindCode,objectTypeCode: osType;plist: prlxPtr): longint;
  1095.  
  1096.       BEGIN
  1097.         WITH plist^ DO
  1098.           BEGIN
  1099.           callbackrequest := getIOObjectCount;
  1100.       callbackData[1]:=longint(handlerKindCode);
  1101.       callbackData[2]:=longint(objectTypeCode);
  1102.           callback(entrypoint);
  1103.           countIOObjects := callbackData[1];
  1104.           END;
  1105.       END;
  1106.  
  1107.     FUNCTION findIndexedIOObjectReference(VAR objectReference: longint;
  1108.                                   handlerKindCode,objectTypeCode: osType;
  1109.                                   index: longint;
  1110.                                   plist: prlxPtr): osErr;
  1111.  
  1112.       BEGIN
  1113.         WITH plist^ DO
  1114.           BEGIN
  1115.           callbackrequest := getIndexedIOObjectReference;
  1116.           callbackData[1] := longint(handlerKindCode);
  1117.           callbackData[2] := longint(objectTypeCode);
  1118.           callbackData[3] := index;
  1119.           callback(entrypoint);
  1120.           objectReference := callbackData[1];
  1121.           findIndexedIOObjectReference := callbackRequest;
  1122.           END;
  1123.       END;
  1124.  
  1125. END.
  1126.